package com.woniuxy.portal.controller;

import com.woniuxy.common.consts.RedisConst;
import com.woniuxy.common.consts.UserConst;
import com.woniuxy.common.enums.impl.BusinessCode;
import com.woniuxy.common.exception.Assert;
import com.woniuxy.portal.model.vo.CartVo;
import com.woniuxy.portal.service.CartService;
import com.woniuxy.portal.utils.JwtUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

@CrossOrigin(origins = "*")
@Slf4j
@Api(tags = "购物车接口")
@RestController
@RequestMapping("/cart")
public class CartController {

    private final CartService cartService;
    private final JwtUtil jwtUtil; //要实现会话跟踪，从Token中获取用户id
    private final RedisTemplate<String, CartVo> redisTemplate;

    @Autowired
    public CartController(CartService cartService, JwtUtil jwtUtil, RedisTemplate<String, CartVo> redisTemplate) {
        this.cartService = cartService;
        this.jwtUtil = jwtUtil;
        this.redisTemplate = redisTemplate;
    }

    /**
     * 获取用户购物车信息
     *
     * @param token 用户认证令牌，从请求头Authorization中获取
     * @return ResponseEntity<CartVo> 包含购物车信息的响应实体
     */
    @ApiOperation("查询购物车")
    @GetMapping("/getCartInfo")
    public ResponseEntity<CartVo> getCartVo(
            @RequestHeader(value = "Authorization") String token) {
        // 验证用户令牌有效性
        boolean result = jwtUtil.validateToken(token);
        Assert.error(!result, BusinessCode.INVALID_TOKEN);

        // 从令牌中解析用户ID
        Long userId = Long.valueOf(jwtUtil.getValue(token, "userId"));

        // 根据用户ID获取购物车信息
        CartVo cart = cartService.getCart(userId);

        return ResponseEntity.ok(cart);
    }

    /**
     * 添加商品到购物车
     *
     * @param token  用户身份验证令牌
     * @param bookId 商品ID
     */
    @ApiOperation("添加购物车")
    @PostMapping("/addCart/{bookId}")
    public void addCart(
            @RequestHeader(value = "Authorization") String token,
            @PathVariable("bookId") Long bookId) {
        // 验证用户令牌有效性
        boolean result = jwtUtil.validateToken(token);
        Assert.error(!result, BusinessCode.INVALID_TOKEN);

        Long userId = Long.valueOf(jwtUtil.getValue(token, "userId"));

//        CartVo cart = cartService.addCart(userId, bookId);
        // 因为添加成功后是直接关闭界面，可以不用返回数据，或者直接void
//        return ResponseEntity.ok(null);

        cartService.addCart(userId, bookId);
    }

    /**
     * 获取我的购物车
     *
     * @param token 用户身份认证令牌
     * @return ResponseEntity<CartVo>购物车信息
     */
    @ApiOperation("结算页面获取购物车")
    @GetMapping("/myCartDetails")
    public ResponseEntity<CartVo> myCartDetails(
            @RequestHeader(name = "Authorization") String token) {
        //获取用户ID
        String userId = jwtUtil.getValue(token, UserConst.USER_ID);
        //从Redis中获取购物车的数据（专用的redisTemplate不用强转）
        CartVo cartvo = redisTemplate.opsForValue().get(RedisConst.USER_CART_PREFIX + ":" + userId);

        return ResponseEntity.ok(cartvo);
    }

    /**
     * 删除购物车中的指定商品
     *
     * @param token  用户身份验证令牌
     * @param bookId 要删除的商品ID
     */
    @ApiOperation("删除购物车")
    @DeleteMapping("/delCart/{bookId}")
    public void delCart(
            @RequestHeader(value = "Authorization") String token,
            @PathVariable("bookId") Long bookId) {
        // 验证用户令牌有效性
        boolean result = jwtUtil.validateToken(token);
        Assert.error(!result, BusinessCode.INVALID_TOKEN);

        Long userId = Long.valueOf(jwtUtil.getValue(token, "userId"));

        cartService.removeCartItem(userId, bookId);
    }

    /**
     * 清空购物车
     * 该方法通过用户令牌验证用户身份，然后清空指定用户的购物车数据
     *
     * @param token 用户身份验证令牌，必须提供有效的JWT令牌
     */
    @ApiOperation("清空购物车")
    @DeleteMapping("/celCart")
    public void celCart(
            @RequestHeader(value = "Authorization") String token) {
        // 验证用户令牌有效性
        boolean result = jwtUtil.validateToken(token);
        Assert.error(!result, BusinessCode.INVALID_TOKEN);

        Long userId = Long.valueOf(jwtUtil.getValue(token, "userId"));

        cartService.clearCart(userId);
    }

}
